/*
 * MailBox.cpp
 *
 *  Created on: 2013. 10. 9.
 *      Author: mega@gamevil.com
 */

#include "../User.h"
#include "Static.h"
#include "MailBox.h"

namespace ProjectZ { namespace NLogic {

MailBox::MailBox()
{
//	Initialize();
}

MailBox::~MailBox()
{
//	Finalize();
}

void
MailBox::Initialize()
{
	//clsMailTree.clear();
}

void
MailBox::Finalize()
{
	auto iter = clsMailTree.begin();

	for (; iter != clsMailTree.end(); ++iter)
	{
		if (NULL == iter->second)
			continue;

		NLogic::Static::InstancePtr()->GETMAILPOOL()->DEL(iter->second);
	}

//	std::for_each(clsMailTree.begin(), clsMailTree.end(), [](MAILTREE::value_type& v) {
//		NLogic::Static::InstancePtr()->GETMAILPOOL()->DEL( v.second );
//	} );

	clsMailTree.clear();
}

bool
MailBox::AddMailData(NLogic::MailBox::Mail * pMail)
{
	if (NULL == pMail)
		return false;

	auto iter = clsMailTree.find(pMail->GetMailSeq());
	if (iter == clsMailTree.end())
		clsMailTree[pMail->GetMailSeq()] = pMail;

	return true;
}

void
MailBox::DelMailData(uint64_t mailSeq)
{
	auto iter = clsMailTree.find(mailSeq);
	if (iter == clsMailTree.end())
		return;

	NLogic::MailBox::Mail * pMail = iter->second;

	clsMailTree.erase(iter);

	NLogic::Static::InstancePtr()->GETMAILPOOL()->DEL(pMail);
}

NLogic::MailBox::Mail *
MailBox::GetMailData(uint64_t mailSeq)
{
	auto iter = clsMailTree.find(mailSeq);
	if (iter == clsMailTree.end())
		return NULL;

	return iter->second;
}

void
MailBox::Mail::Open_Normal(Data & data, User * pUser)
{
	_data		= data;
	_user		= pUser;
}

void
MailBox::Mail::Open_FromDatabase(uint64_t mailSeq, Data & data, User * pUser)
{
	_data		= data;
	_user		= pUser;
	_mailSeq	= mailSeq;
}

MailBox::Mail::Data &
MailBox::Mail::GetData()
{
	return _data;
}

bool
MailBox::Mail::SelectMailShardType(int & shardType)
{
	// 메일을 받는 사람이 자기 자신인 경우
	if (_data.recv_user_seq == _user->GetUserSeq())
	{
		shardType = _user->GetUserInfo().shard_Item_db_type;
		return true;
	}

	::Database::Command::Auto clsAuto(::Database::GETCOMMANDPOOL());
	clsAuto->SetQueryType(::Database::Command::SELECT);
	clsAuto->MakeQuery("SELECT shard_Item_db_type FROM info_user WHERE user_seq = %d", _data.recv_user_seq);

	if (false == ::Database::GETSESSION()->SyncExecute(1, clsAuto))
		return false;

	if (clsAuto->GetErrorIdx() != 0)
		return false;

	while (clsAuto->Next())
	{
		clsAuto->GetRecord() >> shardType;
	}

	return true;
}

bool
MailBox::Mail::InsertDatabaseMail()
{
	int mailShardType = 0;

	if (false == SelectMailShardType(mailShardType))
	{
		PROCESSLOG("%s : false == SelectMailShardType(shardType)", __FUNCTION__);
		return false;
	}

	::Database::Command::Auto clsAuto(::Database::GETCOMMANDPOOL());
	clsAuto->SetQueryType(::Database::Command::INSERT);
	clsAuto->MakeQuery("INSERT INTO data_mail VALUES (NULL,%d,'%s','%s',%d,0,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,%d,'%s',%lld)",
			_data.send_user_seq
			,_data.send_user_nickname.c_str()
			,_data.send_user_imageurl.c_str()
			,_data.recv_user_seq
			,_data.gift_status
			,_data.gift_vcindex
			,_data.zen
			,_data.gold
			,_data.item.bag_type
			,_data.item.bag_slot_number
			,_data.item.quantity
			,_data.item.class_type
			,_data.item.sub_type
			,_data.item.tid
			,_data.item.iconidx
			,_data.item.item_type
			,_data.item.cur_duration
			,_data.item.max_duration
			,_data.item.set_type
			,_data.item.non_identity
			,_data.item.cur_refine_step
			,_data.item.quality
			,_data.item.level
			,_data.item.eff_type[0]
			,_data.item.eff_pos[0]
			,_data.item.eff_value[0]
			,_data.item.eff_type[1]
			,_data.item.eff_pos[1]
			,_data.item.eff_value[1]
			,_data.item.eff_type[2]
			,_data.item.eff_pos[2]
			,_data.item.eff_value[2]
			,_data.item.eff_type[3]
			,_data.item.eff_pos[3]
			,_data.item.eff_value[3]
			,_data.item.eff_type[4]
			,_data.item.eff_pos[4]
			,_data.item.eff_value[4]
			,_data.item.eff_type[5]
			,_data.item.eff_pos[5]
			,_data.item.eff_value[5]
			,_data.item.eff_type[6]
			,_data.item.eff_pos[6]
			,_data.item.eff_value[6]
			,_data.item.open_upgrade_stone_slot
			,_data.item.ability_enhance_rate
			,_data.item.max_enhance_step
			,_data.item.buy_use
			,_data.item.evolve_step
			,_data.item.evolve_max
			,_data.item.evolve_point
			,_data.item.evolve_percent
			,_data.item.evolve_value
			,_data.message.c_str()
			,_data.send_date
			);

	if (false == ::Database::GETSESSION()->SyncExecute(mailShardType, clsAuto))
		return false;

	if( clsAuto->GetErrorIdx() != 0 )
		return false;

	_mailSeq	= clsAuto->GetInsertId();

	return true;
}

bool
MailBox::Mail::UpdateReadStatusDatabaseMail()
{
	::Database::Command::Auto clsAuto(::Database::GETCOMMANDPOOL());
	clsAuto->SetQueryType(::Database::Command::UPDATE);
	clsAuto->MakeQuery("UPDATE data_mail SET mail_status=1 WHERE seq=%lld", _mailSeq);

	if (false == ::Database::GETSESSION()->SyncExecute(_user->GetUserInfo().shard_Item_db_type, clsAuto))
		return false;

	if( clsAuto->GetErrorIdx() != 0 )
		return false;

	_data.mail_status = 1;

	return true;
}

bool
MailBox::Mail::UpdateDeleteStatusDatabaseMail()
{
	::Database::Command::Auto clsAuto(::Database::GETCOMMANDPOOL());
	clsAuto->SetQueryType(::Database::Command::UPDATE);
	clsAuto->MakeQuery("UPDATE data_mail SET mail_status=2 WHERE seq=%lld", _mailSeq);

	if (false == ::Database::GETSESSION()->SyncExecute(_user->GetUserInfo().shard_Item_db_type, clsAuto))
		return false;

	if( clsAuto->GetErrorIdx() != 0 )
		return false;

	 _data.mail_status = 2;

	return true;
}

bool
MailBox::Mail::UpdateGiftStatusDatabaseMail()
{
	::Database::Command::Auto clsAuto(::Database::GETCOMMANDPOOL());
	clsAuto->SetQueryType(::Database::Command::UPDATE);
	clsAuto->MakeQuery("UPDATE data_mail SET gift_status=%d WHERE seq=%lld", _data.gift_status, _mailSeq);

	if (false == ::Database::GETSESSION()->SyncExecute(_user->GetUserInfo().shard_Item_db_type, clsAuto))
		return false;

	if( clsAuto->GetErrorIdx() != 0 )
		return false;

	return true;
}

void
MailBox::Mail::WriteToItemPacket(::Network::Packet * pPacket)
{
	pPacket->MsgCat("%c", _data.item.cur_duration);
	pPacket->MsgCat("%c", _data.item.max_duration);
	pPacket->MsgCat("%c", _data.item.quantity);
	pPacket->MsgCat("%c", _data.item.set_type);
	pPacket->MsgCat("%c", _data.item.non_identity);
	pPacket->MsgCat("%c", _data.item.cur_refine_step);

	pPacket->MsgCat("%c", _data.item.quality);
	pPacket->MsgCat("%c", _data.item.level);

	for( int i=0 ; i<7 ; i++ )
	{
		pPacket->MsgCat("%c", _data.item.eff_type[i]);
		pPacket->MsgCat("%c", _data.item.eff_pos[i]);
		pPacket->MsgCat("%2d", _data.item.eff_value[i]);
	}

	pPacket->MsgCat("%c", _data.item.open_upgrade_stone_slot);
	pPacket->MsgCat("%c", _data.item.ability_enhance_rate);
	pPacket->MsgCat("%c", _data.item.max_enhance_step);
	pPacket->MsgCat("%c", _data.item.buy_use);

	pPacket->MsgCat("%c", _data.item.evolve_step);
	pPacket->MsgCat("%c", _data.item.evolve_max);
	pPacket->MsgCat("%2d", _data.item.evolve_point);
	pPacket->MsgCat("%2d", _data.item.evolve_percent);
	pPacket->MsgCat("%2d", _data.item.evolve_value);
	pPacket->MsgCat("%c", _data.item.class_type);
	pPacket->MsgCat("%c", _data.item.sub_type);
	pPacket->MsgCat("%2d", _data.item.tid);
}

} /*NLogic*/ } /* namespace ProjectZ */
